const express = require("express");
const Group = require("../models/Group");
const GroupMember = require("../models/GroupMember");
const User = require("../models/User");
const auth = require("../middleware/auth");

const router = express.Router();

// 创建小组
router.post("/", auth, async (req, res) => {
  try {
    const { name } = req.body || {};
    if (!name || !String(name).trim()) {
      return res.status(400).json({ message: "缺少小组名称" });
    }
    const group = await Group.create({
      name: String(name).trim(),
      owner: req.user.id,
    });
    await GroupMember.create({
      group: group._id,
      user: req.user.id,
      role: "owner",
      status: "accepted",
    });
    return res
      .status(201)
      .json({ id: group._id, name: group.name, owner: group.owner });
  } catch (err) {
    console.error(err);
    return res.status(500).json({ message: "服务器错误" });
  }
});

// 邀请成员（使用 userId，避免重名）
router.post("/:id/invite", auth, async (req, res) => {
  try {
    const { id } = req.params;
    const { userId } = req.body || {};
    if (!userId) {
      return res.status(400).json({ message: "缺少必要字段: userId" });
    }

    const group = await Group.findById(id).lean();
    if (!group) return res.status(404).json({ message: "小组不存在" });

    // 检查用户权限：组长或管理员可邀请
    const actor = await GroupMember.findOne({
      group: id,
      user: req.user.id,
      status: "accepted",
    }).lean();

    if (!actor || (actor.role !== "owner" && actor.role !== "admin")) {
      return res.status(403).json({ message: "需要组长或管理员权限才能邀请" });
    }

    const invitee = await User.findById(userId).lean();
    if (!invitee) return res.status(404).json({ message: "被邀请用户不存在" });

    // 检查是否已经是成员
    const existingMember = await GroupMember.findOne({
      group: group._id,
      user: invitee._id,
    }).lean();

    if (existingMember) {
      if (existingMember.status === "accepted") {
        return res.status(409).json({
          message: "该用户已经是小组成员",
          memberId: existingMember._id,
          status: "already_member",
        });
      } else if (existingMember.status === "pending") {
        return res.status(409).json({
          message: "该用户已有待处理的邀请",
          memberId: existingMember._id,
          status: "pending_invite",
        });
      }
    }

    // 创建新的邀请
    const member = await GroupMember.create({
      group: group._id,
      user: invitee._id,
      role: "member",
      status: "pending",
      requestType: "invited", // 标记为被邀请
    });

    return res
      .status(200)
      .json({ message: "已发送邀请", memberId: member._id });
  } catch (err) {
    console.error(err);
    return res.status(500).json({ message: "服务器错误" });
  }
});

// 获取待审核的加入申请（组长/管理员）
router.get("/:id/pending", auth, async (req, res) => {
  try {
    const { id } = req.params;

    const group = await Group.findById(id).lean();
    if (!group) return res.status(404).json({ message: "小组不存在" });

    // 检查用户权限：组长或管理员可查看待审核申请
    const actor = await GroupMember.findOne({
      group: id,
      user: req.user.id,
      status: "accepted",
    }).lean();

    if (!actor || (actor.role !== "owner" && actor.role !== "admin")) {
      return res
        .status(403)
        .json({ message: "需要组长或管理员权限才能查看待审核申请" });
    }

    // 获取所有待审核的申请
    const pendingRequests = await GroupMember.find({
      group: id,
      status: "pending",
    })
      .populate("user", "username email")
      .lean();

    // 格式化返回数据
    const requestList = pendingRequests.map((request) => ({
      id: request._id,
      userId: request.user._id,
      username: request.user.username,
      email: request.user.email,
      role: request.role,
      appliedAt: request.createdAt,
    }));

    return res.status(200).json({
      groupId: id,
      pendingRequests: requestList,
      total: requestList.length,
    });
  } catch (err) {
    console.error(err);
    return res.status(500).json({ message: "服务器错误" });
  }
});

// 接受加入申请（组长/管理员）
router.post("/:id/accept/:userId", auth, async (req, res) => {
  try {
    const { id, userId } = req.params;

    const group = await Group.findById(id).lean();
    if (!group) return res.status(404).json({ message: "小组不存在" });

    // 检查用户权限：组长或管理员可审核申请
    const actor = await GroupMember.findOne({
      group: id,
      user: req.user.id,
      status: "accepted",
    }).lean();

    if (!actor || (actor.role !== "owner" && actor.role !== "admin")) {
      return res
        .status(403)
        .json({ message: "需要组长或管理员权限才能审核申请" });
    }

    // 查找并更新申请状态
    const member = await GroupMember.findOneAndUpdate(
      { group: id, user: userId, status: "pending" },
      { $set: { status: "accepted" } },
      { new: true }
    ).lean();

    if (!member) {
      return res.status(404).json({ message: "未找到待审核的申请" });
    }

    return res.status(200).json({ message: "已接受加入申请" });
  } catch (err) {
    console.error(err);
    return res.status(500).json({ message: "服务器错误" });
  }
});

// 拒绝加入申请（组长/管理员）
router.post("/:id/reject/:userId", auth, async (req, res) => {
  try {
    const { id, userId } = req.params;

    const group = await Group.findById(id).lean();
    if (!group) return res.status(404).json({ message: "小组不存在" });

    // 检查用户权限：组长或管理员可审核申请
    const actor = await GroupMember.findOne({
      group: id,
      user: req.user.id,
      status: "accepted",
    }).lean();

    if (!actor || (actor.role !== "owner" && actor.role !== "admin")) {
      return res
        .status(403)
        .json({ message: "需要组长或管理员权限才能审核申请" });
    }

    // 查找并删除申请记录
    const member = await GroupMember.findOneAndDelete({
      group: id,
      user: userId,
      status: "pending",
    }).lean();

    if (!member) {
      return res.status(404).json({ message: "未找到待审核的申请" });
    }

    return res.status(200).json({ message: "已拒绝加入申请" });
  } catch (err) {
    console.error(err);
    return res.status(500).json({ message: "服务器错误" });
  }
});

// 接受邀请（被邀请用户使用）
router.post("/:id/accept", auth, async (req, res) => {
  try {
    const { id } = req.params; // groupId

    // 查找并更新邀请状态（只处理被邀请的情况）
    const updated = await GroupMember.findOneAndUpdate(
      { group: id, user: req.user.id, status: "pending" },
      { $set: { status: "accepted" } },
      { new: true }
    ).lean();

    if (!updated) {
      return res.status(404).json({ message: "未找到待处理的邀请" });
    }

    return res.status(200).json({ message: "已加入小组" });
  } catch (err) {
    console.error(err);
    return res.status(500).json({ message: "服务器错误" });
  }
});

// 我的组列表与待处理邀请
router.get("/mine", auth, async (req, res) => {
  try {
    const memberships = await GroupMember.find({ user: req.user.id })
      .populate("group")
      .lean();

    // 已加入的小组
    const groups = memberships
      .filter((m) => m.status === "accepted" && m.group)
      .map((m) => ({
        id: m.group._id,
        name: m.group.name,
        role: m.role,
        title: m.title || "",
        positionId: m.positionId || null,
      }));

    // 待处理的邀请（被邀请）
    const pendingInvites = memberships
      .filter(
        (m) => m.status === "pending" && m.group && m.requestType === "invited"
      )
      .map((m) => ({
        id: m.group._id,
        name: m.group.name,
        requestType: "invited",
        appliedAt: m.createdAt,
      }));

    // 待处理的申请（主动申请）
    const pendingApplications = memberships
      .filter(
        (m) => m.status === "pending" && m.group && m.requestType === "applied"
      )
      .map((m) => ({
        id: m.group._id,
        name: m.group.name,
        requestType: "applied",
        appliedAt: m.createdAt,
      }));

    return res.status(200).json({
      groups,
      pendingInvites,
      pendingApplications,
    });
  } catch (err) {
    console.error(err);
    return res.status(500).json({ message: "服务器错误" });
  }
});

// 设置成员职位（组长与管理员权限）
router.patch("/:id/members/:userId", auth, async (req, res) => {
  try {
    const { id, userId } = req.params; // groupId, target userId
    const { role, title } = req.body || {};

    const group = await Group.findById(id).lean();
    if (!group) return res.status(404).json({ message: "小组不存在" });

    const actor = await GroupMember.findOne({
      group: id,
      user: req.user.id,
      status: "accepted",
    }).lean();
    if (!actor) return res.status(403).json({ message: "非本组成员" });

    // 权限：
    // - owner：可设置任意成员的 role（含 admin/member）与 title
    // - admin：不可设置 role（不能升降别人角色），只能改 title；也不能改 owner 的任何信息
    if (actor.role !== "owner" && actor.role !== "admin") {
      return res.status(403).json({ message: "需要管理员或组长权限" });
    }

    const target = await GroupMember.findOne({
      group: id,
      user: userId,
      status: "accepted",
    });
    if (!target) return res.status(404).json({ message: "成员不存在或未加入" });

    if (actor.role === "admin") {
      if (role && role !== target.role) {
        return res.status(403).json({ message: "管理员不能修改成员角色" });
      }
      if (String(target.user) === String(group.owner)) {
        return res.status(403).json({ message: "管理员不能修改组长信息" });
      }
    }

    const update = {};
    if (typeof title === "string") update.title = title.trim();
    if (actor.role === "owner" && role) {
      if (!["admin", "member"].includes(role)) {
        return res
          .status(400)
          .json({ message: "无效角色，仅支持 admin/member" });
      }
      // 禁止修改组长的角色
      if (String(target.user) === String(group.owner)) {
        return res.status(403).json({ message: "不能修改组长角色" });
      }
      update.role = role;
    }

    const saved = await GroupMember.findByIdAndUpdate(
      target._id,
      { $set: update },
      { new: true }
    ).lean();
    return res.status(200).json({
      member: {
        id: saved._id,
        user: saved.user,
        role: saved.role,
        title: saved.title || "",
        positionId: saved.positionId || null,
      },
    });
  } catch (err) {
    console.error(err);
    return res.status(500).json({ message: "服务器错误" });
  }
});

// 新增职位（owner/admin）
router.post("/:id/positions", auth, async (req, res) => {
  try {
    const { id } = req.params;
    const { name } = req.body || {};
    if (!name || !String(name).trim()) {
      return res.status(400).json({ message: "缺少职位名称" });
    }
    const group = await Group.findById(id);
    if (!group) return res.status(404).json({ message: "小组不存在" });
    const actor = await GroupMember.findOne({
      group: id,
      user: req.user.id,
      status: "accepted",
    }).lean();
    if (!actor || (actor.role !== "owner" && actor.role !== "admin")) {
      return res.status(403).json({ message: "需要管理员或组长权限" });
    }
    const positionId = group.nextPositionId++;
    group.positions.push({ id: positionId, name: String(name).trim() });
    await group.save();
    return res.status(201).json({ id: positionId, name: String(name).trim() });
  } catch (err) {
    console.error(err);
    return res.status(500).json({ message: "服务器错误" });
  }
});

// 获取职位列表
router.get("/:id/positions", auth, async (req, res) => {
  try {
    const { id } = req.params;
    const actor = await GroupMember.findOne({
      group: id,
      user: req.user.id,
      status: "accepted",
    }).lean();
    if (!actor) return res.status(403).json({ message: "非本组成员" });
    const group = await Group.findById(id).lean();
    if (!group) return res.status(404).json({ message: "小组不存在" });
    return res.status(200).json(group.positions || []);
  } catch (err) {
    console.error(err);
    return res.status(500).json({ message: "服务器错误" });
  }
});

// 重命名/删除职位（owner/admin）
router.patch("/:id/positions/:positionId", auth, async (req, res) => {
  try {
    const { id, positionId } = req.params;
    const { name } = req.body || {};
    const group = await Group.findById(id);
    if (!group) return res.status(404).json({ message: "小组不存在" });
    const actor = await GroupMember.findOne({
      group: id,
      user: req.user.id,
      status: "accepted",
    }).lean();
    if (!actor || (actor.role !== "owner" && actor.role !== "admin")) {
      return res.status(403).json({ message: "需要管理员或组长权限" });
    }
    const pid = Number(positionId);
    const idx = (group.positions || []).findIndex((p) => p.id === pid);
    if (idx === -1) return res.status(404).json({ message: "职位不存在" });
    if (!name || !String(name).trim())
      return res.status(400).json({ message: "缺少职位名称" });
    group.positions[idx].name = String(name).trim();
    await group.save();
    return res.status(200).json(group.positions[idx]);
  } catch (err) {
    console.error(err);
    return res.status(500).json({ message: "服务器错误" });
  }
});

router.delete("/:id/positions/:positionId", auth, async (req, res) => {
  try {
    const { id, positionId } = req.params;
    const group = await Group.findById(id);
    if (!group) return res.status(404).json({ message: "小组不存在" });
    const actor = await GroupMember.findOne({
      group: id,
      user: req.user.id,
      status: "accepted",
    }).lean();
    if (!actor || (actor.role !== "owner" && actor.role !== "admin")) {
      return res.status(403).json({ message: "需要管理员或组长权限" });
    }
    const pid = Number(positionId);
    const before = (group.positions || []).length;
    group.positions = (group.positions || []).filter((p) => p.id !== pid);
    if (group.positions.length === before)
      return res.status(404).json({ message: "职位不存在" });
    await group.save();
    // 清理成员上已使用该职位的引用
    await GroupMember.updateMany(
      { group: id, positionId: pid },
      { $set: { positionId: null } }
    );
    return res.status(200).json({ message: "已删除职位" });
  } catch (err) {
    console.error(err);
    return res.status(500).json({ message: "服务器错误" });
  }
});

// 为成员分配职位
router.patch("/:id/members/:userId/position", auth, async (req, res) => {
  try {
    const { id, userId } = req.params;
    const { positionId } = req.body || {};
    const group = await Group.findById(id).lean();
    if (!group) return res.status(404).json({ message: "小组不存在" });
    const actor = await GroupMember.findOne({
      group: id,
      user: req.user.id,
      status: "accepted",
    }).lean();
    if (!actor || (actor.role !== "owner" && actor.role !== "admin")) {
      return res.status(403).json({ message: "需要管理员或组长权限" });
    }
    const target = await GroupMember.findOne({
      group: id,
      user: userId,
      status: "accepted",
    });
    if (!target) return res.status(404).json({ message: "成员不存在或未加入" });
    if (positionId === null || positionId === undefined) {
      target.positionId = null;
    } else {
      const pid = Number(positionId);
      const exists = (group.positions || []).some((p) => p.id === pid);
      if (!exists) return res.status(404).json({ message: "职位不存在" });
      target.positionId = pid;
    }
    await target.save();
    return res.status(200).json({
      member: {
        id: target._id,
        user: target.user,
        role: target.role,
        title: target.title || "",
        positionId: target.positionId || null,
      },
    });
  } catch (err) {
    console.error(err);
    return res.status(500).json({ message: "服务器错误" });
  }
});

// 踢出成员（仅组长）
router.delete("/:id/members/:userId", auth, async (req, res) => {
  try {
    const { id, userId } = req.params;

    const group = await Group.findById(id).lean();
    if (!group) return res.status(404).json({ message: "小组不存在" });

    // 检查用户权限：组长或管理员可踢出成员
    const actor = await GroupMember.findOne({
      group: id,
      user: req.user.id,
      status: "accepted",
    }).lean();

    if (!actor || (actor.role !== "owner" && actor.role !== "admin")) {
      return res
        .status(403)
        .json({ message: "需要组长或管理员权限才能踢出成员" });
    }

    // 不能踢出自己
    if (String(userId) === String(req.user.id)) {
      return res.status(400).json({ message: "不能踢出自己" });
    }

    // 查找并删除成员记录
    const member = await GroupMember.findOneAndDelete({
      group: id,
      user: userId,
    });

    if (!member) {
      return res.status(404).json({ message: "成员不存在" });
    }

    return res.status(200).json({ message: "已踢出成员" });
  } catch (err) {
    console.error(err);
    return res.status(500).json({ message: "服务器错误" });
  }
});

// 退出小组
router.delete("/:id/leave", auth, async (req, res) => {
  try {
    const { id } = req.params;

    const group = await Group.findById(id).lean();
    if (!group) return res.status(404).json({ message: "小组不存在" });

    // 检查用户是否为小组成员
    const membership = await GroupMember.findOne({
      group: id,
      user: req.user.id,
      status: "accepted",
    });

    if (!membership) {
      return res.status(403).json({ message: "您不是该小组成员" });
    }

    // 组长不能直接退出，需要先转让组长权限或解散小组
    if (membership.role === "owner") {
      return res.status(400).json({
        message: "组长不能直接退出小组，请先转让组长权限或解散小组",
      });
    }

    // 删除成员记录
    await GroupMember.findByIdAndDelete(membership._id);

    return res.status(200).json({ message: "已退出小组" });
  } catch (err) {
    console.error(err);
    return res.status(500).json({ message: "服务器错误" });
  }
});

// 申请加入小组
router.post("/:id/join", auth, async (req, res) => {
  try {
    const { id } = req.params;

    const group = await Group.findById(id).lean();
    if (!group) return res.status(404).json({ message: "小组不存在" });

    // 检查是否已经是成员
    const existingMember = await GroupMember.findOne({
      group: id,
      user: req.user.id,
    }).lean();

    if (existingMember) {
      if (existingMember.status === "accepted") {
        return res.status(409).json({
          message: "您已经是该小组成员",
          memberId: existingMember._id,
          status: "already_member",
        });
      } else if (existingMember.status === "pending") {
        return res.status(409).json({
          message: "您已有待处理的申请",
          memberId: existingMember._id,
          status: "pending_request",
        });
      }
    }

    // 创建加入申请
    const member = await GroupMember.create({
      group: group._id,
      user: req.user.id,
      role: "member",
      status: "pending",
      requestType: "applied", // 标记为主动申请
    });

    return res.status(200).json({
      message: "已发送加入申请，等待组长或管理员审核",
      memberId: member._id,
    });
  } catch (err) {
    console.error(err);
    return res.status(500).json({ message: "服务器错误" });
  }
});

// 获取组成员列表
router.get("/:id/members", auth, async (req, res) => {
  try {
    const { id } = req.params;

    // 检查用户是否为该组成员
    const membership = await GroupMember.findOne({
      group: id,
      user: req.user.id,
      status: "accepted",
    }).lean();

    if (!membership) {
      return res.status(403).json({ message: "非本组成员" });
    }

    // 获取所有已接受的成员
    const members = await GroupMember.find({
      group: id,
      status: "accepted",
    })
      .populate("user", "username email")
      .lean();

    // 格式化返回数据
    const memberList = members.map((member) => ({
      id: member._id,
      userId: member.user._id,
      username: member.user.username,
      email: member.user.email,
      role: member.role,
      title: member.title || "",
      positionId: member.positionId || null,
      joinedAt: member.createdAt,
    }));

    return res.status(200).json({
      groupId: id,
      members: memberList,
      total: memberList.length,
    });
  } catch (err) {
    console.error(err);
    return res.status(500).json({ message: "服务器错误" });
  }
});

// 搜索小组
router.get("/search", auth, async (req, res) => {
  try {
    const { q } = req.query;
    if (!q || !String(q).trim()) {
      return res.status(400).json({ message: "缺少查询参数 q" });
    }

    const searchTerm = String(q).trim();
    const regex = new RegExp(
      searchTerm.replace(/[.*+?^${}()|[\]\\]/g, "\\$&"),
      "i"
    );

    // 搜索小组名称
    const groups = await Group.find({
      name: regex,
    })
      .select("name owner createdAt")
      .populate("owner", "username")
      .limit(20)
      .lean();

    // 格式化返回数据
    const groupList = groups.map((group) => ({
      id: group._id,
      name: group.name,
      owner: {
        id: group.owner._id,
        username: group.owner.username,
      },
      createdAt: group.createdAt,
    }));

    return res.status(200).json({
      groups: groupList,
      total: groupList.length,
    });
  } catch (err) {
    console.error(err);
    return res.status(500).json({ message: "服务器错误" });
  }
});

// 解散小组（仅组长）
router.delete("/:id", auth, async (req, res) => {
  try {
    const { id } = req.params;
    const group = await Group.findById(id).lean();
    if (!group) return res.status(404).json({ message: "小组不存在" });
    if (String(group.owner) !== String(req.user.id)) {
      return res.status(403).json({ message: "仅组长可解散小组" });
    }
    await GroupMember.deleteMany({ group: id });
    await Group.deleteOne({ _id: id });
    return res.status(200).json({ message: "小组已解散" });
  } catch (err) {
    console.error(err);
    return res.status(500).json({ message: "服务器错误" });
  }
});

module.exports = router;
